package com.yvon.grpc.client.service;

import com.yvon.grpc.api.CalculateProto;
import com.yvon.grpc.api.CalculateServiceGrpc;
import com.yvon.grpc.api.NameServersGrpc;
import io.grpc.ManagedChannel;
import io.grpc.stub.StreamObserver;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.annotation.PostConstruct;
import java.util.List;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;

/**
 * @author : wangyufeng
 * @since : 2021-10-19
 */
@Service
@Slf4j
public class CalculateClientService {
    private CalculateServiceGrpc.CalculateServiceStub stub;

    @Autowired
    private ManagedChannel managedChannel;

    @PostConstruct
    private void init() {
        stub = CalculateServiceGrpc.newStub(managedChannel);
    }

    public void getResult(List<Integer> nums) {
        final CountDownLatch countDownLatch = new CountDownLatch(1);

        StreamObserver<CalculateProto.Result> responseObserver = new StreamObserver<CalculateProto.Result>() {
            private int cnt = 0;
            @Override
            public void onNext(CalculateProto.Result result) {
                log.info("客户端：第{}次调用得到的结果为{}", ++cnt, result);
            }

            @Override
            public void onError(Throwable throwable) {
                log.warn("调用出错:{}",throwable.getMessage());
                countDownLatch.countDown();
            }

            @Override
            public void onCompleted() {
                log.info("调用完成");
                countDownLatch.countDown();
            }
        };

        StreamObserver<CalculateProto.Value> requestObserver = stub.getResult(responseObserver);

        for (int num: nums) {
            CalculateProto.Value value = CalculateProto.Value.newBuilder().setValue(num).build();
            requestObserver.onNext(value);

            if (countDownLatch.getCount() == 0) {
                return;
            }


        }

        requestObserver.onCompleted();

        try {
            //如果在规定时间内没有请求完，则让程序停止
            if(!countDownLatch.await(5, TimeUnit.MINUTES)){
                log.warn("未在规定时间内完成调用");
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}
